Terminal tips

The terminal can seem scary at first but after getting used to it there will usually come a tipping point where you find it more convenient than GUI for many tasks. For example: following an online tutorial showing a series of GUI screenshots saying "click-here, check this, edit this" etc is more arduous compared to following a terminal-only tutorial where you just copy some commands into a prompt or paste into a config file.

Also see Headless Server section of this doc for advanced usage.

  • Ctrl + Alt + T to open a new terminal. Ctrl + W to close.
  • You can also switch from your Desktop Environment GUI to a plain TTY terminal by pressing Ctrl + Alt + F3 (Ctrl + Alt + F2 in Gnome or Ctrl + Alt + F1 in KDE to return to GUI), useful if your GUI goes haywire.
  • Your desktop Linux distro will come with some form of GUI terminal app such as Gnome Terminal or Konsole (you can install other terminal apps like Tilix or Terminator with better features like tiling). The terminal app runs a Shell program inside it on startup (default usually /bin/bash). For headless installations like Ubuntu Server, you can ONLY use the terminal as there is no GUI.
  • A Shell is a command interpreter; it provides a prompt to enter text commands and display text output from the command/programs. Various commands are either built into the Shell or names of executable programs or scripts that run as children of the Shell (often located in a bin folder listed in your PATH variable).
    • The common type of shell is /bin/bash.
    • Many advanced users like zsh.
    • The most primitive type of shell is /bin/sh.
    • The most user-friendly shell is fish, my favourite. Suggest checking it out after learning the basics in your default terminal.
  • A shell script is a text file containing a list of commands to execute by a particular shell interpreter. Depending on the shell, you can include if statements and possibly even loops and functions like a primitive programming language. Bash shell script is default and has a .sh file extension. Fish uses .fish extension. The first line of any script is called the shebang line, and tells your OS which shell or interpreter should be used to run it. Example shebang lines:
    • #!/bin/bash - bash script
    • #!/usr/bin/python - Python script
  • Most shells will run some initialization shell script by default on startup.
    • The whole desktop environment GUI shell will run ~/.profile upon login.
    • Bash runs ~/.bashrc on startup.
    • You can add your global configuration and environment variables in these files.
  • You can pipe output of one command into another once using | symbol. For example cat readme.txt would show the contents of readme.txt file in the terminal, however you can instead pipe the contents into the less tool to allow scrolling through a large file cat readme.txt | less
  • You can also pipe to and from files using:
    • {command} > filename.txt to pipe output of command into a file (overwrite).
    • {command} >> filename.txt to pipe output of command into a file (append).
    • {command} < filename.txt to pipe file contents into a command.

Basic commands

Must-know commands. Get to know these by heart:

CommandDescription
tldr {command}Not essential but recommend to help you learn more quickly, so I mention this first. Type sudo apt install tldr if you dont have it. Shows quick practical information about any command. A potentially more powerful alternative that I now use instead of tldr is cht.sh
man {command}Show manual page for the command, with long instructions on how to use it
pwdPrint working directory
lsList contents of directory (add -a to show hidden, -l to show details). A much improved alternative is exa. exa -al@ shows all files and details.
cd {dir}Change directory
rm {file}Delete file (add -rf for directory and contents) DANGEROUS COMMAND - deletes without confirmation, and no recycle bin!! Add -i for a confirmation or replace with a command that moves files to a .trash folder instead. Another good option is trash-cli ⭐ (pip install trash-cli)
cp {source-file} {dest-file}Copy file or directory to another location. Multiple source files can be specified. (add -r to include directories). Use rsync for large numbers of files and to monitor progress and in some cases much faster speeds.
mv {source-file} {dest-file}Move file or directory to another location (note: hidden files excluded by * operator, run shopt -s dotglob to change this option)
mv {old-name} {new-name}Rename a file or directory
mkdir {dir}Create a new directory
clearClear terminal output. Shortcut: Ctrl + L
exitClose the terminal

Advanced commands

Learn these gradually. Use a web-search man or tldr for help when needed:

CommandDescription
apropos {search-term}Useful for finding commands. Searches through all manual pages, for commands related to search-term.
aliasShows all current aliases. Used to assign a long command to run a short one to reduce typing e.g. alias c=clear Add to your .basrc to persist.
echoPrint some text to terminal. Also print contents of variables e.g. echo $PATH
rsyncSynchronize a source directory to destination, can be used as a cp replacement for large/many files and also works with remote servers. Add -ah --progress to show progress while copying
lessDisplay text from a file or stream in scrollable terminal. more is another option but only allows one way scrolling and may be slow due to loading a whole file at once
catConcatenate/show text from a file or stream
ifconfigShow IP address, MAC and other network settings
wgetDownload a file from URL
curlSend/Receive data via URLs (e.g. using POST or GET)
lnCreate symbolic link
findFind files e.g: find ~/ -iname *.desktop Also run a command on each search result add:-exec cp "{}" /home/shantanu/tosend \;
locateFind files quickly by searching file index database. In case some recent files are missing, you can manually update database sudo updatedb
sedFind and replace in text
awkSplit text into fields and filter by keywords
cutSelect and display fields from text
grepRegular expression (and pipe | operator). Can also be used for "Find in Files" operation, i.e. to recursively find all text files containing a given string e.g. grep -rIH 'TEXT_TO_FIND' (I = ignores binary files)
whichFind location of an executable on path
dfList mounted volumes ans usage, use -h to make it more readable.
mount/umountMount or unmount a volume, such as a USB drive. Type fdisk -l or lsblk to list available block devices for mounting. Type findmnt or mount to show currently mounted devices.
chmodChange file attributes and permissions (executable, readonly etc)
chownChange file ownership
watchRun a process every 2 seconds (configurable) and monitor its output/errors.
psList processes. -A to list all running processes.
top or htopReal-time process and performance viewer/manager
kill or pkillKill or send other signals to processes
tailDisplay the last 10 lines of a text file, monitor it and display any changes - perfect for monitoring a log file. e.g. tail -f /var/log/app/status.log

More Terminal Inspiration: Terminal all-time greats

Initialisation scripts

When a terminal is launched, there are various scripts that run automatically on startup and can be different depending on the type of session (e.g. Bash, Zsh or Fish etc), and whether login shell (where you enter user/password) or non-login shell (e.g. launching a terminal window after already logged in as a user).

You can add things like:

  • Environment variables e.g. export MYHOME="$HOME/Documents/myhome"
  • Add executables to PATH e.g. export PATH="$PATH:/path/to/apps/bin"
  • Command aliases e.g. alias c=clear
  • Set default settings, e.g. colors and format for the prompt
  • Autorun programs e.g. show current weather or a cool message/picture on startup

Which script file you add them to depends on whether you want the change to be specific to a user, specific to a session type, or system wide for any session.

User-specific

  • Login shell:

    • ~/.profile - default for all sessions
    • ~/.bash_login - if it exists, replaces and overrides above for bash sessions
    • ~/.bash_profile - if it exists, replaces and overrides all above for bash sessions
  • Non-login shell:

    • ~/.bashrc - specific to bash session
    • ~/.config/fish/config.fish - specific to fish session

System-wide

  • Login shell: /etc/profile - for all sessions
  • Non-login shell:
    • /etc/bash.bashrc - specific to bash session
    • /etc/fish/config.fish - specific to fish session

More information.

Copy and Paste in terminal windows:

Option 1: Using the desktop-environment clipboard

  • Copy: Select text by dragging mouse over text or double click to select word. The press Ctrl+Shift+C to copy. Alternatively, Ctrl+RightClick brings up a context menu in many terminals that allows copying.
  • Paste: Paste into the terminal by pressing Ctrl+Shift+V. Alternatively, Ctrl+RightClick brings up a context menu in many terminals that allows pasting.

Option 2: use the terminals own separate internal clipboard:

  • Copy: Select text by dragging mouse over text or double click to select word. When you let go of the mouse button, the selected text is copied to the internal clipboard.
  • Paste: Move cursor to destination and click the Middle mouse button to paste.

Option 3: using commands

  • use xclip and xsel commands to pipe text to and from either the terminal or system keyboards.

Generic Hotkeys

Unless specified, these should work on most shells like Bash and Fish. Consult the docs for your shell for more.

KeyOperation
Ctrl+LClear the screen
Ctrl+CClear the currently entered command, or terminate currently running application
Ctrl+KClear the currently entered command from cursor to end of line
Ctrl+UClear the currently entered command from cursor to beginning
Ctrl+WDelete the current word under cursor until beginning of word
Alt+DDelete the current word under cursor until end of word
Alt+L(FISH ONLY) List files in current directory

Move hidden files by default (in a bash shell with mv)

When you first use mv to move or rename folders containing files, you may notice it skips hidden files (i.e. names starting with .), which is a concern! You can change this default setting using shopt to edit shell options:

  • Set (enable) show/move hidden files⭐: shopt -s dotglob nullglob
  • Un-set (disable) show/move hidden files: shopt -u dotglob nullglob

Super user (sudo)

Commands are normally run as the current logged in user. For super-user permissions run with sudo before the command. OR to switch the current terminal session to root: sudo -s (limit this use, for security) (note su command doesn’t work in Ubuntu by default as root login is disabled) User terminal is denoted by a $ and root/super-user terminal is denoted by #

When you run a sudo command, sometimes you want to keep the current users environment variables (e.g. settings from .bashrc or vim config). To do this, use sudo -E. For example, this is especially useful if you heavily customized your vim text editor for your current user and you want to be able to use the same customizations when editing as root.

WARNING: Dont be tempted to do everything as a super user or root! This is NOT like a Windows user with admin priviledges. When you run as root/sudo you are literally running programs and creating files as a different user and when you switch back you may not be able to access them! You may also break the system or have security problems when over-using root access. Stick to your regular user and only use root when needed.

Start a {command} in the terminal and allow it to continue in background after closing

{command} &
disown

GZ (gunzip) or extract a file

Zip a file or dir into archive.tar.gz (multiple files and dirs can be specified)

tar -czf archive.tar.gz {file-to-zip}

Unzip archive.tar.gz into (optional) destination dir

tar -xzf archive.tar.gz -C {dest-dir}

Add v flag for verbose mode (list all files processed)

ZIP archiving and UNZIP extraction

sudo apt install zip unzip

zip singlefile.zip original_file
zip -r directory.zip original_dir
unzip {zipfile} -d {destination-directory}

Foreground and background app in terminal

Press Ctrl + Z in console will set current app to background (stopped)

To go back to it, type fg

To allow the stopped background app to continue in the background, type bg

You can list child process of current shell using ($$ means current shell process):

pgrep -P $$

Then disown them to allow running after closing the shell session

Nano: Simple default text editor in terminal

Use nano {filename} for a simple file editor or vim (or a fork like neovim) if you want a lot more power and efficiency (but a steep learning curve).

Nano keyboard shortcuts: Can seem unconventional due to restrictions of key combos in terminal If you don’t like them, you may be able to use Select/Copy/Paste of your terminal instead, see Copy and Paste section above.

ShortcutFunction
Alt + UUndo (shown as M-U in the terminal UI)
Alt + ERedo (shown as M-E)
Ctrl + WSearch
Alt + WSearch again
Ctrl + XExit (it will ask to save, press y)
Shift + {arrow}Select text
Alt + 6Copy
Ctrl + KCut
Ctrl + UPaste
Esc + 3Comment out selected block (default with #)

Recommended settings: Edit settings: sudo nano /etc/nanorc Uncomment the following to enable line numbers, mouse, wordwrap and auto-indent:

set mouse
set linenumbers
set softwrap
set autoindent

Micro: The Best intuitive text editor in terminal

If you want a great text editor which is easy to use and powerful, and you don't want to learn Vim go with micro ⭐. If you want to know why it is so "intuitive", basically keyboard shortcuts like ctrl+Q ctrl+C ctrl+V ctrl+X ctrl+F ctrl+A etc all do what you expect them to do, with zero learning curve. Here is the download link (can also be installed via apt package manager, but the snap or repo releases are more up to date. Personally I used brew to install it).

Set micro as default console editor (type which micro to get PATH_TO_MICRO):

sudo update-alternatives --install /usr/bin/editor editor PATH_TO_MICRO 50
sudo update-alternatives --config editor
sudo update-alternatives --install /usr/bin/sensible-editor sensible-editor PATH_TO_MICRO 50
sudo update-alternatives --config sensible-editor

You should also set the EDITOR=micro environment variable if you want certain shell commands to use it as default.

Copy/Paste with SSH session to host clipboard:

Unlike Vim and Nano, Micro captures the mouse in the terminal, even when using SSH. Therefore to copy and paste text to/from a terminal SSH session host using mouse, you need to hold shift and mouse select, then ctrl + shift + C or shift + right click to copy to host clipboard.

If you want to copy and paste multi-line selected text when in SSH from one file to another, do this within the same micro session, just use ctrl + c to copy to internal micro clipboard then press ctrl + o to open the second file and ctrl + v to paste it.

Vim: Powerful text editor in terminal

Vim is good to learn if you want to do a lot of editing of text files, config or code, however it has a steep learning curve and is completely unusable without at least knowing some basic, such as the modes listed below.

It is a text editor with roots in the 70s, and is designed to be ultra-efficient by avoiding use of the mouse, and ultra-extensible with plugins for myriad useful functionality (see section below for essential starter plugins). It achieves this through reusing keys depending on what mode the editor is in (much easier to visualize the current mode with plugins like airline).

I prefer the neovim fork, as it's been refactored to unlock future potential. A key difference with neovim is the config file is located ~/.config/nvim/init.vim instead of ~/.vimrc. Another fork to check out is SpaceVim, which takes a distro-like apprach to Vim with plugins as layers depending on the type of project you are working on.

If you like neovim, try neovim-qt, a GUI wrapper which adds a few features such as drag and drop a file to open, a file tree browser, and basic mouse support (cursor, selecting/resizing sub windows and scrolling). Another upcoming GUI with VS Code style functionality using neovim, is Onivim 2.

Basic modes of Vim include:

  • Normal (DEFAULT mode at start, enter commands, navigate text quickly)
    Hit ESC to return to this mode any time. To get you started, some easy commands:

    • Search: Hit / and type to search text, press enter then n or N to navigate back and forth results.
    • Undo: u Redo: Ctrl + r
    • Delete (aka Cut) lines:
      • x - delete current character
      • 3x - delete 3 characters
      • dw - delete current word (try W for WORDs)
      • dd - delete current line
      • 5dd - delete five lines
      • d$ - delete to end of line
      • d0 - delete to beginning of line
      • :1,.d - delete to beginning of file
      • :.,$d - delete to end of file
    • Switch between different panels: Ctrl + w, w
  • Command (global commands e.g w {name} = save, q = quit, e {name} = open)
    Hit : from Normal mode to activate.

  • Insert (usual text entry mode, Type text as you would expect)
    Hit i from Normal mode to activate.

  • Visual Hit v (or V for line-wise) from Normal mode. Allows visually selecting text with arrow keys.

    • y - yank (copy) selection
    • 3yy - yank (copy) 3 lines
    • 2yw - yank (copy) 2 words (try W for WORDs)
    • p - paste after cursor
    • P - paste before cursor
    • f} - select until next occurance of } on current line (can be any character)
    • F< - select until previous occurance of < on current line (can be any character)

Recommended Settings:

For Neovim, suggest adding this line to sync Vim clipboard register to system clipboard when using yank and paste:

set clipboard+=unnamedplus

Vim Plugins:

FIRST suggest to install a plugin manager such as vim-plug Add add a few good plugins to your vim config file like:

Plug 'tpope/vim-sensible'
Plug 'vim-airline/vim-airline'
Plug 'preservim/nerdtree'
Plug 'vim-airline/vim-airline-themes'
Plug 'preservim/nerdtree'
Plug 'tpope/vim-fugitive'
Plug 'scrooloose/syntastic'
Plug 'ctrlpvim/ctrlp.vim'
Plug 'lifepillar/vim-cheat40'
Plug 'ycm-core/YouCompleteMe'
# YCM: Run 'python3 install.py --all' in plugin dir (.local/share/nvim/plugged/youcompleteme/) to complete installation or update.
#YCM: If using neovim, also run 'pip install --upgrade pynvim' to enable Python support

Remember to run :PlugInstall within Vim to complete installation after adding any plugins to. Update plugins - :PlugUpdate Update vim-plug itself - :PlugUpgrade Delete a plugin - Remove it from your vim config then run :PlugClean

More:

  • A list of AWESOME plugins for Vim
  • A guy explaining his advanced customizations
  • Setting up advanced fast auto complete (YouCompleteMe plugin and language server, remember to complete installation run python3 install.py --all in the plugins installed directory - normally ~/.local/share/nvim/plugged/youcompleteme/)

Open working directory in a GUI file browser window

xdg-open .

This also opens any file or folder using the default app.

Environment variables and path

To add to EVs and path, you can edit a number of files depending on requirements: https://superuser.com/questions/789448/choosing-between-bashrc-profile-bash-profile-etc Note that if you modify .profile, this will only be reloaded AFTER logging in again, so you must either restart the PC or run source ~/.profile to load it immediately. If you modify .bashrc, you just need to restart the terminal session or source it.

Note for Fish shell > v3.2, you can use fish_add_path to permanently add to the path. e.g. fish_add_path /usr/local/go/bin

Cool Terminals

Alternatives to the built in terminal app (e.g. Gnome Terminal or Konsole). To change your default terminal:

sudo update-alternatives --config x-terminal-emulator
  • Tilix - GPU accelerated, tiling terminal, search, pwd manager, optional ‘Quake’ mode.⭐
  • hyper - Modern extensible Electron based terminal
  • Alacritty - GPU accelerated, claims to be the fastest, but many question that
  • cool-retro-term - Cool looking retro CRT style terminal
  • Yakuake - ‘Quake’ style drop down terminal for KDE using Konsole

Cool Shells

  • The popular posix compliant shell alternative to Bash: Zsh
    • A UX-focused shell (my daily driver): Fish (Friendly Interactive SHell)⭐
      • Type fish_config to launch web config GUI or edit the files (config.fish) in ~/.config/fish/
        • Oh My Fish package and theme manager (omf theme to find themes)
        • Explore what fish can do online without installing.

Cool terminal addons

  • Check out this guide for a ready-to-go beautification or install various options as per below.

  • Sensible defaults for bash

  • A beautiful UX-focused shell prompt: Starship can be added to Bash, Fish, Zsh or many others ⭐